home *** CD-ROM | disk | FTP | other *** search
/ Nebula 2 / Nebula Two.iso / Apps / ScreenSavers / darken / VidLev.c < prev   
C/C++ Source or Header  |  1995-06-12  |  12KB  |  546 lines

  1. /*
  2.  *    VidLev.c - get/set display's video level
  3.  */
  4.  
  5. /*
  6.  * Copyright 1991 Purdue Research Foundation, West Lafayette, Indiana
  7.  * 47907.  All rights reserved.
  8.  *
  9.  * Written by Vic Abell, Purdue University Computing Center.
  10.  *
  11.  * This software is not subject to any license of the American Telephone
  12.  * and Telegraph Company or the Regents of the University of California.
  13.  *
  14.  * Permission is granted to anyone to use this software for any purpose on
  15.  * any computer system, and to alter it and redistribute it freely, subject
  16.  * to the following restrictions:
  17.  *
  18.  * 1. Neither the author nor Purdue University are responsible for any
  19.  *    consequences of the use of this software.
  20.  *
  21.  * 2. The origin of this software must not be misrepresented, either by
  22.  *    explicit claim or by omission.  Credit to the author and Purdue
  23.  *    University must appear in documentation and sources.
  24.  *
  25.  * 3. Altered versions must be plainly marked as such, and must not be
  26.  *    misrepresented as being the original software.
  27.  *
  28.  * 4. This notice may not be removed or altered.
  29.  */
  30.  
  31. #ifndef lint
  32. static char copyright[] =
  33. "@(#) Copyright 1991 Purdue Research Foundation.\nAll rights reserved.\n";
  34. #endif
  35.  
  36. /*
  37.  *    Usage:
  38.  *
  39.  *    VidLev [-b|-h|-r{a|e|r}|-s{a|e|r}] [-t] [-p path] [value(s)]
  40.  *
  41.  *        where:
  42.  *
  43.  *        -b    Blank and repeatedly reblank the screen until stopped.
  44.  *            If stopped with a SIGHUP, the pre-blanking EVS and 
  45.  *            NVRAM brightness values are restored.  The process
  46.  *            ID is written to a file at the path specified with
  47.  *            the -p option (default = BIN/VidLev.pid).
  48.  *
  49.  *            The value parameters specify the initial and subsequent
  50.  *            reblanking intervals in seconds (defaults = 45 and 600).
  51.  *
  52.  *            NOTE: requires root (or NOBODY) permission.
  53.  *
  54.  *        -h    Display help.
  55.  *
  56.  *        -p path    Specify the path to the file to which the process ID
  57.  *            is written.  This option is only legitimate if the
  58.  *            the -b option is specified.  The default process ID
  59.  *            file path is BIN/VidLev.pid.
  60.  *
  61.  *        -ra    Report EVS and NVRAM brightness values to STDOUT.
  62.  *            This is the default action for a root (or NOBODY)
  63.  *            caller.
  64.  *        -re    Report the event driver (EVS) brightness to STDOUT.
  65.  *            This is the default action for a non-root caller.
  66.  *        -rr    Report the NVRAM brightness to STDOUT.
  67.  *
  68.  *        -sa    Set EVS and NVRAM brightness values. 
  69.  *        -se    Set the event driver (EVS) brightness.
  70.  *        -sr    set the NVRAM brightness.
  71.  *        
  72.  *        -t    Set terse reporting -- no titles.
  73.  *
  74.  *        value    This optional parameter specifies:
  75.  *
  76.  *            -b       reblanking intervale in seconds
  77.  *            -s[a|e|r]  brightness value:
  78.  *                   0 or dim     darkest
  79.  *                   61 or bright     brightest
  80.  *                   1 - 59     relative brightness between
  81.  *                         darkest (0) and brightest (61)
  82.  *
  83.  *    Note:    The default action for a root (or NOBODY) caller is "-ra";
  84.  *        non-root, "-re".
  85.  */
  86.  
  87. #include <c.h>
  88. #include <stdio.h>
  89. #include <stdlib.h>
  90. #include <string.h>
  91. #include <signal.h>
  92. #include <sys/file.h>
  93. #include <sys/ioctl.h>
  94. #include <sys/types.h>
  95. #include "missing.h"
  96. #include <dev/m68k/evsio.h>
  97. #include <dev/m68k/video.h>
  98.  
  99. #if    !defined(BIN)
  100. #define    BIN        "/usr/local/etc"
  101. #endif
  102. #define    EDEVICE        "/dev/evs0"
  103. #define    EVS        1
  104. #define    IREPEAT        45
  105. #define    NVRAM        2
  106. #define PIDDIGITS    6
  107. #define    REPEAT        600
  108. #define VIDLEVPID    "/VidLev.pid"
  109. #define    VDEVICE        "/dev/vid0"
  110.  
  111. extern int errno;
  112. extern char *sys_errlist[];
  113. extern char *optarg;
  114. extern int optind;
  115.  
  116. int Efd = -1;                /* EVS file descriptor */
  117. int Evsval;                /* original EVS value */
  118. struct nvram_info Nvram;        /* NVRAM information */
  119. int Pfd = -1;                /* PID file descriptor */
  120. char *Pidpath = BIN VIDLEVPID;        /* PID file path */
  121. char *Pn;                /* program name */
  122. int Vfd = -1;                /* video (NVRAM) file descriptor */
  123.  
  124. void setevs(), setnvram(), sighup();
  125.  
  126.  
  127.  
  128.  
  129. main(argc, argv)
  130.     int argc;
  131.     char *argv[];
  132. {
  133.     int c;                /* character buffer */
  134.     int err = 0;            /* argument error count */
  135.     unsigned int ireblank = IREPEAT;
  136.                     /* initial reblank interval */
  137.     int mblank = 0;            /* blank mode */
  138.     int mhelp = 0;            /* help mode */
  139.     int mread = 0;            /* read mode */
  140.     int mset = 0;            /* set mode */
  141.     int mterse = 0;            /* terse mode */
  142.     int mtype = EVS;        /* mode type */
  143.     char pid[PIDDIGITS+2];        /* process ID */
  144.     unsigned int reblank = REPEAT;    /* reblanking interval */
  145.     unsigned int sleeptm;        /* sleep time */
  146.     uid_t uid;            /* user ID */
  147.     int val = -1;            /* value paramter */
  148. /*
  149.  * Save program name.
  150.  */
  151.     if ((Pn = strrchr(argv[0], '/')) != NULL)
  152.         Pn++;
  153.     else
  154.         Pn = argv[0];
  155. /*
  156.  * Process arguments.
  157.  */
  158.     while ((c = getopt(argc, argv, "bhp:r:s:t")) != EOF) {
  159.         switch (c) {
  160.  
  161.         case 'b':
  162.             mblank = 1;
  163.             break;
  164.         case 'h':
  165.             mhelp = 1;
  166.             break;
  167.         case 'p':
  168.             Pidpath = optarg;
  169.             break;
  170.         case 'r':
  171.         case 's':
  172.             if (c == 'r')
  173.                 mread = 1;
  174.             else
  175.                 mset = 1;
  176.             switch (*optarg) {
  177.  
  178.             case 'a':
  179.                 mtype = EVS | NVRAM;
  180.                 break;
  181.             case 'e':
  182.                 mtype = EVS;
  183.                 break;
  184.             case 'r':
  185.                 mtype = NVRAM;
  186.                 break;
  187.             default:
  188.                 (void) fprintf(stderr,
  189.                     "%s: illegal -r/-s option (%c)\n",
  190.                     Pn, *optarg);
  191.                 err++;
  192.             }
  193.             break;
  194.         
  195.         case 't':
  196.             mterse = 1;
  197.             break;
  198.  
  199.         case '?':
  200.             err++;
  201.             break;
  202.         default:
  203.             (void) fprintf(stderr, "%s: unknown option (%c)\n",
  204.                 Pn, c);
  205.             err++;
  206.         }
  207.     }
  208. /*
  209.  * Process value argument.
  210.  */
  211.     if (optind <= (argc - 1)) {
  212.         if (mblank) {
  213.             ireblank = atoi(argv[optind++]);
  214.             if (optind <= (argc - 1))
  215.                 reblank = atoi(argv[optind++]);
  216.             else {
  217.                 (void) fprintf(stderr,
  218.                     "%s: no reblank interval specified\n",
  219.                     Pn);
  220.                 err++;
  221.             }
  222.             val = BRIGHT_MIN;
  223.         } else if (mset) {
  224.             if (strcmp(argv[optind], "dim") == 0) {
  225.                 val = BRIGHT_MIN;
  226.                 optind++;
  227.             } else if (strcmp(argv[optind], "bright") == 0) {
  228.                 val = BRIGHT_MAX;
  229.                 optind++;
  230.             } else {
  231.                 val = atoi(argv[optind]);
  232.                 optind++;
  233.             }
  234.         }
  235.     }
  236.     if (optind < argc) {
  237.         (void) fprintf(stderr, "%s: extra (unknown) options\n", Pn);
  238.         err++;
  239.     }
  240. /*
  241.  * Check for sensible arguments.  Set the default if no modes specified.
  242.  */
  243.     uid = getuid();
  244.     if ((c = mblank + mset + mread + mhelp) == 0) {
  245.         mread = 1;
  246.  
  247. #if    defined(NOBODY)
  248.         mtype = (uid == 0 || uid == NOBODY) ? (EVS | NVRAM) : EVS;
  249. #else
  250.         mtype = getuid() ? EVS : (EVS | NVRAM);
  251. #endif
  252.  
  253.     } else if (c != 1) {
  254.         (void) fprintf(stderr, "%s: use only one of -b, -h, -r, -s\n",
  255.             Pn);
  256.         err++;
  257.     }
  258.  
  259. #if    defined(NOBODY)
  260.     if (mblank && uid != 0 && uid != NOBODY)
  261. #else
  262.     if (mblank && getuid() != 0)
  263. #endif
  264.  
  265.     {
  266.  
  267. #if    defined(NOBODY)
  268.         (void) fprintf(stderr, "%s: must be UID 0 or %d to use -b\n",
  269.             Pn, NOBODY);
  270. #else
  271.         (void) fprintf(stderr, "%s: must be root to use -b\n", Pn);
  272. #endif
  273.  
  274.         err++;
  275.     }
  276.  
  277. #if    defined(NOBODY)
  278.     if (((mread || mset) && (mtype & NVRAM)) && uid != 0 && uid != NOBODY)
  279. #else
  280.     if (((mread || mset) && (mtype & NVRAM)) && getuid() != 0)
  281. #endif
  282.  
  283.     {
  284.         (void) fprintf(stderr,
  285.  
  286. #if    defined(NOBODY)
  287.             "%s: must be UID 0 or %d to read or set NVRAM\n",
  288.                 Pn, NOBODY);
  289. #else
  290.             "%s: must be root to read or set NVRAM\n", Pn);
  291. #endif
  292.  
  293.         err++;
  294.     }
  295. /*
  296.  * Display help and exit if help requested or if errors detected.
  297.  */
  298.     if (err || mhelp) {
  299.         (void) fprintf(stderr,
  300.           "%s usage: [-b|-h|-r{a|e|r}|-s{a|e|r}] [-t] [-p path]", Pn);
  301.         (void) fprintf(stderr, " [value(s)]\n");
  302.         (void) fprintf(stderr,
  303.  
  304. #if    defined(NOBODY)
  305.           "  -b       blank mode (must be UID 0 or %d)\n", NOBODY);
  306. #else
  307.           "  -b       blank mode (must be root)\n");
  308. #endif
  309.  
  310.         (void) fprintf(stderr,
  311.           "           value1 = initial repeat seconds (default = %d)\n",
  312.         IREPEAT);
  313.         (void) fprintf(stderr,
  314.           "           value2 = subsequent repeat seconds (default = %d)\n",
  315.         REPEAT);
  316.         (void) fprintf(stderr,
  317.           "  -h       display help\n");
  318.         (void) fprintf(stderr,
  319.           "  -p path  specify PID file path, default = %s\n",
  320.             BIN VIDLEVPID);
  321.         (void) fprintf(stderr,
  322.           "  -ra      report EVS and NVRAM brightnesses to STDOUT\n");
  323.         (void) fprintf(stderr,
  324.  
  325. #if    defined(NOBODY)
  326.           "           (must be UID 0 or %d) (their default action)\n",
  327.             NOBODY);
  328. #else
  329.           "           (must be root) (root default action)\n");
  330. #endif
  331.  
  332.         (void) fprintf(stderr,
  333.           "  -re      report EVS brightness to STDOUT");
  334.         (void) fprintf(stderr,
  335.           " (non-root default action)\n");
  336.         (void) fprintf(stderr,
  337.  
  338. #if    defined(NOBODY)
  339.           "  -rr      report NVRAM brightness to STDOUT (must be UID 0 or %d)\n", NOBODY);
  340. #else
  341.           "  -rr      report NVRAM brightness to STDOUT (must be root)\n");
  342. #endif
  343.  
  344.         (void) fprintf(stderr,
  345.           "  -sa      set EVS and NVRAM brightnesses from value");
  346.         (void) fprintf(stderr,
  347.  
  348. #if    defined(NOBODY)
  349.           " (must be UID 0 or %d)\n", NOBODY);
  350. #else
  351.           " (must be root)\n");
  352. #endif
  353.  
  354.         (void) fprintf(stderr,
  355.           "  -se      set EVS brightness from value\n");
  356.         (void) fprintf(stderr,
  357.  
  358. #if    defined(NOBODY)
  359.           "  -sr      set NVRAM brightness from value (must be UID 0 or %d)\n", NOBODY);
  360. #else
  361.           "  -sr      set NVRAM brightness from value (must be root)\n");
  362. #endif
  363.  
  364.         (void) fprintf(stderr,
  365.           "  -t       terse output\n");
  366.         (void) fprintf(stderr,
  367.           "  value    optional value(s) for -b and -s[a|e|r]\n");
  368.         if (err)
  369.         exit(1);
  370.         exit(0);
  371.     }
  372. /*
  373.  * Open EVS device.
  374.  */
  375.     if (mblank || ((mset || mread) && (mtype & EVS))) {
  376.         if ((Efd = open(EDEVICE, O_RDWR, 0)) == CERROR) {
  377.             (void) fprintf(stderr, "%s: can't open %s: %s\n",
  378.                 Pn, EDEVICE, sys_errlist[errno]);
  379.             exit(1);
  380.         }
  381.     }
  382. /*
  383.  * Open video (NVRAM) device.
  384.  */
  385.     if (mblank || ((mset || mread) && (mtype & NVRAM))) {
  386.         if ((Vfd = open(VDEVICE, O_RDWR, 0)) == CERROR) {
  387.             (void) fprintf(stderr, "%s: can't open %s: %s\n",
  388.                 Pn, VDEVICE, sys_errlist[errno]);
  389.             close_exit(1);
  390.         }
  391.     }
  392. /*
  393.  * Read current values.
  394.  */
  395.     if (mblank || mread) {
  396.         if (mblank || (mtype & EVS)) {
  397.             if (ioctl(Efd, EVSIOCB, &Evsval) == CERROR) {
  398.                 (void) fprintf(stderr,
  399.                     "%s: can't EVSIOCB %s: $s\n",
  400.                     Pn, EDEVICE, sys_errlist[errno]);
  401.                 close_exit(1);
  402.             }
  403.         }
  404.         if (mblank || (mtype & NVRAM)) {
  405.             if (ioctl(Vfd, DKIOCGNVRAM, &Nvram) == CERROR) {
  406.                 (void) fprintf(stderr,
  407.                     "%s: can't DKIOCGNVRAM %s: $s\n",
  408.                     Pn, VDEVICE, sys_errlist[errno]);
  409.                 close_exit(1);
  410.             }
  411.         }
  412.     }
  413. /*
  414.  * Print values.
  415.  */
  416.     if (mread) {
  417.         if (mtype & EVS) {
  418.             if (mterse)
  419.                 (void) printf("%d\n", Evsval);
  420.             else
  421.                 (void) printf("%s: EVS brightness = %d\n",
  422.                     Pn, Evsval);
  423.         }
  424.         if (mtype & NVRAM) {
  425.             if (mterse)
  426.                 (void) printf("%d\n", Nvram.ni_brightness);
  427.             else
  428.                 (void) printf("%s: NVRAM brightness = %d\n",
  429.                     Pn, Nvram.ni_brightness);
  430.         }
  431.         close_exit(0);
  432.     }
  433. /*
  434.  * Set new values.
  435.  */
  436.     if (mset) {
  437.         if (mtype & EVS)
  438.             setevs(val);
  439.         if (mtype & NVRAM)
  440.             (void) setnvram(val);
  441.         close_exit(0);
  442.     }
  443. /*
  444.  * Perform blank function:
  445.  *
  446.  *    1.  Isolate from parent process.
  447.  *    2.  Record process ID in Pidpath[].
  448.  *    3.  Enable SIGHUP interrupt.
  449.  *    4.  Reduce NVRAM brightness to BRIGHT_MIN.
  450.  *    5.  Repeat step 2 every reblank seconds, because loginwindow
  451.  *        changes the brightness 30 minutes after logout.
  452.  */
  453.     if (mblank) {
  454.         if (fork())
  455.             close_exit(0);
  456.         if ((Pfd = open(Pidpath, O_RDWR|O_CREAT|O_TRUNC, 0644)) < 0) {
  457.             (void) printf("%s: can't open %s: %s\n",
  458.                 Pn, Pidpath, sys_errlist[errno]);
  459.             close_exit(1);
  460.         }
  461.         (void) sprintf(pid, "%*d\n", PIDDIGITS, getpid());
  462.         (void) write(Pfd, pid, strlen(pid));
  463.         (void) close(Pfd);
  464.         Pfd = -1;
  465.         (void) signal(SIGHUP, sighup);
  466.         for (sleeptm = ireblank;; sleeptm = reblank) {
  467.             (void) setnvram(val);
  468.             (void) sleep(sleeptm);
  469.         }
  470. /* NOTREACHED */
  471.     }
  472.     (void) fprintf(stderr, "%s: no action to perform\n", Pn);
  473.     exit(1);
  474. }
  475.  
  476.  
  477. /*
  478.  * close_exit(v) - close all files and exit(v)
  479.  */
  480.  
  481. close_exit(v)
  482. {
  483.     if (Efd >= 0) {
  484.         (void) close(Efd);
  485.         Efd = -1;
  486.     }
  487.     if (Pfd >= 0) {
  488.         (void) close(Pfd);
  489.         Pfd = -1;
  490.     }
  491.     if (Vfd >= 0) {
  492.         (void) close(Vfd);
  493.         Vfd = -1;
  494.     }
  495.     exit(v);
  496. }
  497.  
  498.  
  499. /*
  500.  * setevs(val) set EVS brightness to val
  501.  */
  502.  
  503. void
  504. setevs(val)
  505.     int val;
  506. {
  507.     if (ioctl(Efd, EVSIOSB, &val) == CERROR) {
  508.         (void) fprintf(stderr, "%s: can't EVSIOSB %s: $s\n",
  509.             Pn, EDEVICE, sys_errlist[errno]);
  510.         close_exit(1);
  511.     }
  512. }
  513.  
  514.  
  515. /*
  516.  * setnvram(val) - set NVRAM brightness to val
  517.  */
  518.  
  519. void
  520. setnvram(val)
  521.     int val;
  522. {
  523.     if (ioctl(Vfd, DKIOCBRIGHT, &val) == CERROR) {
  524.         (void) fprintf(stderr, "%s: can't DKIOCBRIGHT %s: %s",
  525.             Pn, VDEVICE, sys_errlist[errno]);
  526.         close_exit(1);
  527.     }
  528. }
  529.  
  530.  
  531. /*
  532.  * sighup() - process SIGHUP
  533.  */
  534.  
  535. void
  536. sighup()
  537. {
  538.     int val;
  539.     
  540.     (void) setevs(Evsval);
  541.     val = Nvram.ni_brightness;
  542.     (void) setnvram(val);
  543.     (void) unlink(Pidpath);
  544.     close_exit(0);
  545. }
  546.